// "箭头函数表达式" ( An arrow function expression )

function outer(){
    console.log( arguments );
    // 形参列表 => 函数体
    let add = (a,b) => {
        console.log( arguments );
        let c = a + b ;
        return c ;
    }
    let result = add( 5 , 6 );
    console.log( result );
}

outer('hello','kaifamiao','yunchuangdongli');

console.log( '- - - - - - - - - - - - - - - - - - - -' );

let sum = (a,b,c)=>{
    return a + b + c ;
}

// 当作普通函数使用
console.log( sum( 10 , 20 , 30 ) );

// 作构造函数使用
// new sum(); // TypeError: sum is not a constructor

// 若形参只有一个，则可以省略形参列表中的小括号
let opposite = num => {
    return -num ;
}

console.log( opposite( -5 ) );
console.log( opposite( 5 ) );

// 若函数体只有一行代码则可以省略函数体大括号
let showTime = () => console.log( new Date() )
showTime();

// 如果仅存的单行代码中有 return 则可以将其省略
let subtract = (a,b) => a - b ;
console.log( subtract( 6.95 , 3.14 ) );

function Student( id , name ){
    this.id = id ;
    this.name = name ;

    let arrow = ()=>{
        // 在箭头函数中使用 this 时，this 表示宿主环境中的 this
        console.log( this );
    }
    arrow();
}

let s = new Student( 1001 , '小姜同学' );
console.log( s );

// 在箭头函数中使用 rest参数
let summation = (...params) => {
    console.log( params );
    let total = 0 ;
    for( let i = 0 , n = params.length ; i < n ; i++ ){
        total += params[ i ];
    }
    return total ;
}

console.log( summation( 10 , 20 , 30 ) );
console.log( summation( 1 , 2 , 3 , 4 , 5 ) );

// 总结:
// 1、箭头函数内不可通过 arguments 获得该函数本身的实参
//    (箭头函数内如果使用 arguments 则表示该箭头函数所在宿主的实参)
// 2、箭头函数不可当作构造函数来使用
// 3、仅当形参只有一个时才可以省略形参列表中的小括号
// 4、若函数体仅剩单行代码，则可以省略函数体大括号
//    若仅存的单行代码中有 return 则可以将 return 省略
// 5、箭头函数内不可用 this 访问自身实例，而是表示宿主环境中的 this